package com.urchin.avatarhero.util.cal;

import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.TreeMap;

import android.annotation.TargetApi;
import android.app.Activity;
import android.content.ContentResolver;
import android.database.Cursor;
import android.net.Uri;
import android.os.Build;
import android.provider.CalendarContract.Calendars;

/**********************************************************************
AvatarHero - A task management RPG Android Application
Copyright (C) 2013  Peter Clay

This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.

This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
GNU General Public License for more details.

You should have received a copy of the GNU General Public License
along with this program.  If not, see <http://www.gnu.org/licenses/>.
***********************************************************************/

public class CalendarHandler {
	// Projection array. Creating indices for this array instead of doing
	// dynamic lookups improves performance.
	public static final String[] EVENT_PROJECTION = new String[] {
	    Calendars._ID,                           // 0
	    Calendars.ACCOUNT_NAME,                  // 1
	    Calendars.CALENDAR_DISPLAY_NAME,         // 2
	    Calendars.OWNER_ACCOUNT                  // 3
	};
	// The indices for the projection array above.
	private static final int PROJECTION_ID_INDEX = 0;
	private static final int PROJECTION_ACCOUNT_NAME_INDEX = 1;
	private static final int PROJECTION_DISPLAY_NAME_INDEX = 2;
	private static final int PROJECTION_OWNER_ACCOUNT_INDEX = 3;
	public static final int NUM_TO_DISP = 3;
	public static final int CAL_DATA_LEN = 7;
	private static final long YEAR_IN_MILLI = 31556900000L;
	Activity act = null;
	public static SimpleDateFormat dformatter = new SimpleDateFormat("MM/dd/yy HH:mm");
	Calendar cal = Calendar.getInstance();
	String dispname = "default";
	public long curtime = System.currentTimeMillis();
	Uri events = null;
	Uri instances = null;
	
	public CalendarHandler(Activity a) {
		act = a;
	}
	
	@SuppressWarnings("deprecation")
	@TargetApi(14)
	public TreeMap<Integer,CalEvent> getEvents() { 
		TreeMap<Integer,CalEvent> elist = new TreeMap<Integer,CalEvent>();
		
		//Variables
		String[] projection = null;
		Cursor cursor = null;
		
		if(Build.VERSION.SDK_INT >= 14) {
			ContentResolver cr = act.getContentResolver();
			events = Calendars.CONTENT_URI;   
			String selection = "((" + Calendars.ACCOUNT_NAME + " = ?) AND (" 
					+ Calendars.ACCOUNT_TYPE + " = ?) AND ("
					+ Calendars.OWNER_ACCOUNT + " = ?))";
			String[] selectionArgs = new String[] {"sampleuser@gmail.com", "com.google",
				"sampleuser@gmail.com"}; 

			// Submit the query and get a Cursor object back. 
			cursor = cr.query(events, EVENT_PROJECTION, selection,  selectionArgs, null);
		} else if(Build.VERSION.SDK_INT >= 7) {
			// Setup for 2.1 support
			if(Build.VERSION.SDK_INT <= 7) {							// Old Software
				events = Uri.parse("content://calendar/events");
			} else {
				events = Uri.parse("content://com.android.calendar/events");
			}
			projection = new String[] { "_id", "title", "description", "dtstart", "dtend", "eventLocation", "calendar_id" };
			if(events != null) {
				cursor = act.managedQuery(events,projection,null,null,null);
			}
		}
			
		if(cursor != null) {
			// Use the cursor to set the events to the HashMap
			cursor.moveToFirst();	    
		    for (int i = 0; i < cursor.getCount(); i++) {
		    	CalEvent edata = new CalEvent();
		        edata.title = cursor.getString(1);
		        edata.description = cursor.getString(2);
		        edata.startime = cursor.getLong(3);
		        edata.endtime = cursor.getLong(4);
		        edata.location = cursor.getString(5);
		        edata.id = cursor.getInt(0);
		        edata.calid = cursor.getInt(6);
	
		        elist.put(i, edata);
		        cursor.moveToNext();
		    }
		    cursor.close();
		}
		
	    return elist;
	}
	
	@SuppressWarnings("deprecation")
	@TargetApi(14)
	public TreeMap<Integer,CalInstance> getInstances() {
		TreeMap<Integer,CalInstance> ilist = new TreeMap<Integer,CalInstance>();
		
		//Variables
		String[] projection = null;
		@SuppressWarnings("deprecation")
		Cursor cursor = null;
		
		// Choose the correct way to load the events
		if(Build.VERSION.SDK_INT >= 14) {
			ContentResolver cr = act.getContentResolver();
			instances = Calendars.CONTENT_URI;   
			String selection = "((" + Calendars.ACCOUNT_NAME + " = ?) AND (" 
					+ Calendars.ACCOUNT_TYPE + " = ?) AND ("
					+ Calendars.OWNER_ACCOUNT + " = ?))";
			String[] selectionArgs = new String[] {"sampleuser@gmail.com", "com.google",
				"sampleuser@gmail.com"}; 

			// Submit the query and get a Cursor object back. 
			cursor = cr.query(events, EVENT_PROJECTION, selection,  selectionArgs, null);
		} else if(Build.VERSION.SDK_INT >= 7) {
			// Setup for 2.1 support
			if(Build.VERSION.SDK_INT <= 7) {							// Old Software
				instances = Uri.parse("content://calendar/instances/when/0/" + String.valueOf(curtime + YEAR_IN_MILLI));
			} else {
				instances = Uri.parse("content://com.android.calendar/instances/when/0/" + String.valueOf(curtime + YEAR_IN_MILLI));
			}
			projection = new String[] { "_id", "event_id", "begin", "end" };
			if(instances != null) {
				cursor = act.managedQuery(instances,projection,null,null,null);
			}
		}
		
		// Use the cursor to set the events to the HashMap
		if(cursor != null) {
			cursor.moveToFirst();	    
		    for (int i = 0; i < cursor.getCount(); i++) {
		    	CalInstance idata = new CalInstance();
		        idata.id = cursor.getInt(0);			// Instance ID
		        idata.eventid = cursor.getInt(1);		// Event ID
		        idata.starttime = cursor.getLong(2);	// Begin time
		        idata.endtime = cursor.getLong(3);		// End time
	
		        ilist.put(i, idata);
		        cursor.moveToNext();
		    }
		    cursor.close();
		}
	    
	    return ilist;
	}
	
	public ArrayList<CalBlob> buildCalData(TreeMap<Integer,CalEvent> elist, TreeMap<Integer,CalInstance> ilist) {
		ArrayList<CalBlob> rank = new ArrayList<CalBlob>();		// Rank and flist should be tied by j index
		
		for (int i = 0; i < ilist.size(); i++) {			// For each instance
			CalBlob cdata = new CalBlob();
			cdata.instanceid = ilist.get(i).id;
			cdata.eventid = ilist.get(i).eventid;
			cdata.starttime = ilist.get(i).starttime;
			cdata.endtime = ilist.get(i).endtime;
			
			for(int j = 0;j < elist.size(); j++) {
				if(elist.get(j).id == cdata.eventid) {		// If the Event ID matches, fill in event info
			        cdata.title = elist.get(j).title;
			        cdata.description = elist.get(j).description;
			        cdata.location = elist.get(j).location;
			        cdata.calid = elist.get(j).calid;
				}
			}
			
			// Ranking
			if(i == 0) {		// Initial element
    			rank.add(i, cdata);		// Add the String array to the array list
    		} else {

    			int k = 0;
				for(k = 0;k<rank.size();k++) {
		    		if(cdata.starttime < rank.get(k).starttime) {		// If the event time is less than the next lowest
		    			rank.add(k, cdata);
		    			break;
		    		}
		    	}
				if(k>=rank.size()) {	// Add to the end of list
					rank.add(cdata);
				}
    		}
		}
		//Toast.makeText(act.getApplicationContext(),"Import: <" + String.valueOf(rank.size()) + ">",Toast.LENGTH_SHORT).show();

		return rank;
	}
	
	// Setters and Getters

	public SimpleDateFormat getDformatter() {
		return dformatter;
	}

	public void setDformatter(SimpleDateFormat dformatter) {
		this.dformatter = dformatter;
	}
	
}
